<!DOCTYPE html>
<html lang="zh-CN">
<head>
  <meta charset="UTF-8">
<meta name="viewport" content="width=device-width">
<meta name="theme-color" content="#222"><meta name="generator" content="Hexo 6.3.0">

  <link rel="apple-touch-icon" sizes="180x180" href="/images/apple-touch-icon-next.png">
  <link rel="icon" type="image/png" sizes="32x32" href="/images/favicon-32x32-next.png">
  <link rel="icon" type="image/png" sizes="16x16" href="/images/favicon-16x16-next.png">
  <link rel="mask-icon" href="/images/logo.svg" color="#222">

<link rel="stylesheet" href="/css/main.css">



<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.2.1/css/all.min.css" integrity="sha256-Z1K5uhUaJXA7Ll0XrZ/0JhX4lAtZFpT6jkKrEDT0drU=" crossorigin="anonymous">
  <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.1.1/animate.min.css" integrity="sha256-PR7ttpcvz8qrF57fur/yAx1qXMFJeJFiA6pSzWi0OIE=" crossorigin="anonymous">

<script class="next-config" data-name="main" type="application/json">{"hostname":"example.com","root":"/","images":"/images","scheme":"Muse","darkmode":false,"version":"8.14.1","exturl":false,"sidebar":{"position":"left","display":"post","padding":18,"offset":12},"copycode":{"enable":false,"style":null},"bookmark":{"enable":false,"color":"#222","save":"auto"},"mediumzoom":false,"lazyload":false,"pangu":false,"comments":{"style":"tabs","active":null,"storage":true,"lazyload":false,"nav":null},"stickytabs":false,"motion":{"enable":true,"async":false,"transition":{"menu_item":"fadeInDown","post_block":"fadeIn","post_header":"fadeInDown","post_body":"fadeInDown","coll_header":"fadeInLeft","sidebar":"fadeInUp"}},"prism":false,"i18n":{"placeholder":"搜索...","empty":"没有找到任何搜索结果：${query}","hits_time":"找到 ${hits} 个搜索结果（用时 ${time} 毫秒）","hits":"找到 ${hits} 个搜索结果"},"path":"/search.xml","localsearch":{"enable":true,"trigger":"auto","top_n_per_article":-1,"unescape":false,"preload":false}}</script><script src="/js/config.js"></script>

    <meta name="description" content="这里我做的这份笔记的意义仅仅是记录下自己学习Spring的历程，既不是对官方API的深入解释，也不一定是对新手友好的、知识点详尽的一份学习清单。  1 Spring IoC容器和Bean简介1.1 了解IOC1.1.1 Bean什么是Bean?  在Spring中，构成应用程序主干并由Spring IoC容器管理的对象称为bean。Bean是由SpringIoC容器实例化，组装和管理的对象。">
<meta property="og:type" content="article">
<meta property="og:title" content="Spring 学习笔记1  ——  IOC容器 I （IOC容器、DI依赖注入）">
<meta property="og:url" content="http://example.com/2021/07/01/Spring%20%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B01%20%20%E2%80%94%E2%80%94%20%20IOC%E5%AE%B9%E5%99%A8%20I%20%EF%BC%88IOC%E5%AE%B9%E5%99%A8%E3%80%81DI%E4%BE%9D%E8%B5%96%E6%B3%A8%E5%85%A5%EF%BC%89/index.html">
<meta property="og:site_name" content="JsyBlog">
<meta property="og:description" content="这里我做的这份笔记的意义仅仅是记录下自己学习Spring的历程，既不是对官方API的深入解释，也不一定是对新手友好的、知识点详尽的一份学习清单。  1 Spring IoC容器和Bean简介1.1 了解IOC1.1.1 Bean什么是Bean?  在Spring中，构成应用程序主干并由Spring IoC容器管理的对象称为bean。Bean是由SpringIoC容器实例化，组装和管理的对象。">
<meta property="og:locale" content="zh_CN">
<meta property="article:published_time" content="2021-06-30T16:00:00.000Z">
<meta property="article:modified_time" content="2021-10-14T16:41:04.513Z">
<meta property="article:author" content="SongyangJi">
<meta property="article:tag" content="Spring核心">
<meta property="article:tag" content="JavaEE">
<meta name="twitter:card" content="summary">


<link rel="canonical" href="http://example.com/2021/07/01/Spring%20%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B01%20%20%E2%80%94%E2%80%94%20%20IOC%E5%AE%B9%E5%99%A8%20I%20%EF%BC%88IOC%E5%AE%B9%E5%99%A8%E3%80%81DI%E4%BE%9D%E8%B5%96%E6%B3%A8%E5%85%A5%EF%BC%89/">



<script class="next-config" data-name="page" type="application/json">{"sidebar":"","isHome":false,"isPost":true,"lang":"zh-CN","comments":true,"permalink":"http://example.com/2021/07/01/Spring%20%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B01%20%20%E2%80%94%E2%80%94%20%20IOC%E5%AE%B9%E5%99%A8%20I%20%EF%BC%88IOC%E5%AE%B9%E5%99%A8%E3%80%81DI%E4%BE%9D%E8%B5%96%E6%B3%A8%E5%85%A5%EF%BC%89/","path":"2021/07/01/Spring 学习笔记1  ——  IOC容器 I （IOC容器、DI依赖注入）/","title":"Spring 学习笔记1  ——  IOC容器 I （IOC容器、DI依赖注入）"}</script>

<script class="next-config" data-name="calendar" type="application/json">""</script>
<title>Spring 学习笔记1  ——  IOC容器 I （IOC容器、DI依赖注入） | JsyBlog</title>
  








  <noscript>
    <link rel="stylesheet" href="/css/noscript.css">
  </noscript>
</head>

<body itemscope itemtype="http://schema.org/WebPage" class="use-motion">
  <div class="headband"></div>

  <main class="main">
    <div class="column">
      <header class="header" itemscope itemtype="http://schema.org/WPHeader"><div class="site-brand-container">
  <div class="site-nav-toggle">
    <div class="toggle" aria-label="切换导航栏" role="button">
        <span class="toggle-line"></span>
        <span class="toggle-line"></span>
        <span class="toggle-line"></span>
    </div>
  </div>

  <div class="site-meta">

    <a href="/" class="brand" rel="start">
      <i class="logo-line"></i>
      <p class="site-title">JsyBlog</p>
      <i class="logo-line"></i>
    </a>
  </div>

  <div class="site-nav-right">
    <div class="toggle popup-trigger" aria-label="搜索" role="button">
        <i class="fa fa-search fa-fw fa-lg"></i>
    </div>
  </div>
</div>



<nav class="site-nav">
  <ul class="main-menu menu"><li class="menu-item menu-item-home"><a href="/" rel="section"><i class="fa fa-home fa-fw"></i>首页</a></li><li class="menu-item menu-item-tags"><a href="/tags/" rel="section"><i class="fa fa-tags fa-fw"></i>标签</a></li><li class="menu-item menu-item-categories"><a href="/categories/" rel="section"><i class="fa fa-th fa-fw"></i>分类</a></li><li class="menu-item menu-item-archives"><a href="/archives/" rel="section"><i class="fa fa-archive fa-fw"></i>归档</a></li>
      <li class="menu-item menu-item-search">
        <a role="button" class="popup-trigger"><i class="fa fa-search fa-fw"></i>搜索
        </a>
      </li>
  </ul>
</nav>



  <div class="search-pop-overlay">
    <div class="popup search-popup"><div class="search-header">
  <span class="search-icon">
    <i class="fa fa-search"></i>
  </span>
  <div class="search-input-container">
    <input autocomplete="off" autocapitalize="off" maxlength="80"
           placeholder="搜索..." spellcheck="false"
           type="search" class="search-input">
  </div>
  <span class="popup-btn-close" role="button">
    <i class="fa fa-times-circle"></i>
  </span>
</div>
<div class="search-result-container no-result">
  <div class="search-result-icon">
    <i class="fa fa-spinner fa-pulse fa-5x"></i>
  </div>
</div>

    </div>
  </div>

</header>
        
  
  <aside class="sidebar">

    <div class="sidebar-inner sidebar-nav-active sidebar-toc-active">
      <ul class="sidebar-nav">
        <li class="sidebar-nav-toc">
          文章目录
        </li>
        <li class="sidebar-nav-overview">
          站点概览
        </li>
      </ul>

      <div class="sidebar-panel-container">
        <!--noindex-->
        <div class="post-toc-wrap sidebar-panel">
            <div class="post-toc animated"><ol class="nav"><li class="nav-item nav-level-1"><a class="nav-link" href="#1-Spring-IoC%E5%AE%B9%E5%99%A8%E5%92%8CBean%E7%AE%80%E4%BB%8B"><span class="nav-number">1.</span> <span class="nav-text">1 Spring IoC容器和Bean简介</span></a><ol class="nav-child"><li class="nav-item nav-level-2"><a class="nav-link" href="#1-1-%E4%BA%86%E8%A7%A3IOC"><span class="nav-number">1.1.</span> <span class="nav-text">1.1 了解IOC</span></a><ol class="nav-child"><li class="nav-item nav-level-3"><a class="nav-link" href="#1-1-1-Bean"><span class="nav-number">1.1.1.</span> <span class="nav-text">1.1.1 Bean</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#1-1-2-IOC%E5%AE%B9%E5%99%A8"><span class="nav-number">1.1.2.</span> <span class="nav-text">1.1.2 IOC容器</span></a></li></ol></li><li class="nav-item nav-level-2"><a class="nav-link" href="#1-2-%E5%AE%B9%E5%99%A8%E6%A6%82%E8%BF%B0"><span class="nav-number">1.2.</span> <span class="nav-text">1.2 容器概述</span></a><ol class="nav-child"><li class="nav-item nav-level-3"><a class="nav-link" href="#1-2-1-%E9%85%8D%E7%BD%AE%E5%85%83%E6%95%B0%E6%8D%AE"><span class="nav-number">1.2.1.</span> <span class="nav-text">1.2.1 配置元数据</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#1-2-2-%E5%AE%9E%E4%BE%8B%E5%8C%96%E5%AE%B9%E5%99%A8"><span class="nav-number">1.2.2.</span> <span class="nav-text">1.2.2 实例化容器</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#1-2-3-%E4%BD%BF%E7%94%A8%E5%AE%B9%E5%99%A8"><span class="nav-number">1.2.3.</span> <span class="nav-text">1.2.3  使用容器</span></a></li></ol></li><li class="nav-item nav-level-2"><a class="nav-link" href="#1-3-Bean"><span class="nav-number">1.3.</span> <span class="nav-text">1.3 Bean</span></a><ol class="nav-child"><li class="nav-item nav-level-3"><a class="nav-link" href="#1-3-1-Bean-%E7%9A%84%E5%91%BD%E5%90%8D"><span class="nav-number">1.3.1.</span> <span class="nav-text">1.3.1 Bean 的命名</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#1-3-2-Bean-%E7%9A%84%E5%AE%9E%E4%BE%8B%E5%8C%96"><span class="nav-number">1.3.2.</span> <span class="nav-text">1.3.2 Bean 的实例化</span></a></li></ol></li><li class="nav-item nav-level-2"><a class="nav-link" href="#1-4-%E4%BE%9D%E8%B5%96%EF%BC%88Dependencies%EF%BC%89"><span class="nav-number">1.4.</span> <span class="nav-text">1.4 依赖（Dependencies）</span></a><ol class="nav-child"><li class="nav-item nav-level-3"><a class="nav-link" href="#1-4-1-%E4%BE%9D%E8%B5%96%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.1.</span> <span class="nav-text">1.4.1 依赖注入</span></a><ol class="nav-child"><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-1-1-Constructor-%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.1.1.</span> <span class="nav-text">1.4.1.1 Constructor 注入</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-1-2-Setter-%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.1.2.</span> <span class="nav-text">1.4.1.2 Setter 注入</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-1-3-Factory%E6%96%B9%E6%B3%95%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.1.3.</span> <span class="nav-text">1.4.1.3 Factory方法注入</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-1-4-%E5%BE%AA%E7%8E%AF%E4%BE%9D%E8%B5%96%E9%97%AE%E9%A2%98"><span class="nav-number">1.4.1.4.</span> <span class="nav-text">1.4.1.4 循环依赖问题</span></a></li></ol></li><li class="nav-item nav-level-3"><a class="nav-link" href="#1-4-2-%E4%BE%9D%E8%B5%96%E6%B3%A8%E5%85%A5%E7%9A%84%E7%BB%86%E8%8A%82"><span class="nav-number">1.4.2.</span> <span class="nav-text">1.4.2 依赖注入的细节</span></a><ol class="nav-child"><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-2-1-%E7%9C%9F%E5%80%BC%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.2.1.</span> <span class="nav-text">1.4.2.1 真值注入</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-2-2-Bean%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.2.2.</span> <span class="nav-text">1.4.2.2 Bean注入</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-2-3-%E7%A9%BA%E4%B8%B2%E5%92%8CNULL"><span class="nav-number">1.4.2.3.</span> <span class="nav-text">1.4.2.3 空串和NULL</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-2-4-%E6%95%B0%E7%BB%84%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.2.4.</span> <span class="nav-text">1.4.2.4 数组注入</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-2-5-List%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.2.5.</span> <span class="nav-text">1.4.2.5 List注入</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-2-6-Map%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.2.6.</span> <span class="nav-text">1.4.2.6 Map注入</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-2-7-Set%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.2.7.</span> <span class="nav-text">1.4.2.7 Set注入</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-2-8-Properties%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.2.8.</span> <span class="nav-text">1.4.2.8 Properties注入</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-2-9-p-%E5%91%BD%E5%90%8D%E7%A9%BA%E9%97%B4%E4%B8%8Ec-%E5%91%BD%E5%90%8D%E7%A9%BA%E9%97%B4"><span class="nav-number">1.4.2.9.</span> <span class="nav-text">1.4.2.9 p-命名空间与c-命名空间</span></a></li><li class="nav-item nav-level-4"><a class="nav-link" href="#1-4-2-10-%E5%A4%8D%E5%90%88%E5%B1%9E%E6%80%A7%E5%90%8D%E7%A7%B0"><span class="nav-number">1.4.2.10.</span> <span class="nav-text">1.4.2.10 复合属性名称</span></a></li></ol></li><li class="nav-item nav-level-3"><a class="nav-link" href="#1-4-3-depends-on"><span class="nav-number">1.4.3.</span> <span class="nav-text">1.4.3 depends-on</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#1-4-4-Bean%E7%9A%84%E6%87%92%E5%8A%A0%E8%BD%BD"><span class="nav-number">1.4.4.</span> <span class="nav-text">1.4.4 Bean的懒加载</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#1-4-5-%E8%87%AA%E5%8A%A8%E8%A3%85%E9%85%8D"><span class="nav-number">1.4.5.</span> <span class="nav-text">1.4.5 自动装配</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#1-4-6-%E6%96%B9%E6%B3%95%E6%B3%A8%E5%85%A5"><span class="nav-number">1.4.6.</span> <span class="nav-text">1.4.6 方法注入</span></a></li></ol></li></ol></li></ol></div>
        </div>
        <!--/noindex-->

        <div class="site-overview-wrap sidebar-panel">
          <div class="site-author animated" itemprop="author" itemscope itemtype="http://schema.org/Person">
  <p class="site-author-name" itemprop="name">SongyangJi</p>
  <div class="site-description" itemprop="description"></div>
</div>
<div class="site-state-wrap animated">
  <nav class="site-state">
      <div class="site-state-item site-state-posts">
        <a href="/archives/">
          <span class="site-state-item-count">251</span>
          <span class="site-state-item-name">日志</span>
        </a>
      </div>
      <div class="site-state-item site-state-categories">
          <a href="/categories/">
        <span class="site-state-item-count">45</span>
        <span class="site-state-item-name">分类</span></a>
      </div>
      <div class="site-state-item site-state-tags">
          <a href="/tags/">
        <span class="site-state-item-count">109</span>
        <span class="site-state-item-name">标签</span></a>
      </div>
  </nav>
</div>

        </div>
      </div>
    </div>

    
  </aside>


    </div>

    <div class="main-inner post posts-expand">


  


<div class="post-block">
  
  

  <article itemscope itemtype="http://schema.org/Article" class="post-content" lang="zh-CN">
    <link itemprop="mainEntityOfPage" href="http://example.com/2021/07/01/Spring%20%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B01%20%20%E2%80%94%E2%80%94%20%20IOC%E5%AE%B9%E5%99%A8%20I%20%EF%BC%88IOC%E5%AE%B9%E5%99%A8%E3%80%81DI%E4%BE%9D%E8%B5%96%E6%B3%A8%E5%85%A5%EF%BC%89/">

    <span hidden itemprop="author" itemscope itemtype="http://schema.org/Person">
      <meta itemprop="image" content="/images/avatar.gif">
      <meta itemprop="name" content="SongyangJi">
    </span>

    <span hidden itemprop="publisher" itemscope itemtype="http://schema.org/Organization">
      <meta itemprop="name" content="JsyBlog">
      <meta itemprop="description" content="">
    </span>

    <span hidden itemprop="post" itemscope itemtype="http://schema.org/CreativeWork">
      <meta itemprop="name" content="Spring 学习笔记1  ——  IOC容器 I （IOC容器、DI依赖注入） | JsyBlog">
      <meta itemprop="description" content="">
    </span>
      <header class="post-header">
        <h1 class="post-title" itemprop="name headline">
          Spring 学习笔记1  ——  IOC容器 I （IOC容器、DI依赖注入）
        </h1>

        <div class="post-meta-container">
          <div class="post-meta">
    <span class="post-meta-item">
      <span class="post-meta-item-icon">
        <i class="far fa-calendar"></i>
      </span>
      <span class="post-meta-item-text">发表于</span>

      <time title="创建时间：2021-07-01 00:00:00" itemprop="dateCreated datePublished" datetime="2021-07-01T00:00:00+08:00">2021-07-01</time>
    </span>
    <span class="post-meta-item">
      <span class="post-meta-item-icon">
        <i class="far fa-calendar-check"></i>
      </span>
      <span class="post-meta-item-text">更新于</span>
      <time title="修改时间：2021-10-15 00:41:04" itemprop="dateModified" datetime="2021-10-15T00:41:04+08:00">2021-10-15</time>
    </span>
    <span class="post-meta-item">
      <span class="post-meta-item-icon">
        <i class="far fa-folder"></i>
      </span>
      <span class="post-meta-item-text">分类于</span>
        <span itemprop="about" itemscope itemtype="http://schema.org/Thing">
          <a href="/categories/Spring/" itemprop="url" rel="index"><span itemprop="name">Spring</span></a>
        </span>
    </span>

  
</div>

        </div>
      </header>

    
    
    
    <div class="post-body" itemprop="articleBody">
        <blockquote>
<p>这里我做的这份笔记的意义仅仅是记录下自己学习Spring的历程，既不是对官方API的深入解释，也不一定是对新手友好的、知识点详尽的一份学习清单。</p>
</blockquote>
<h1 id="1-Spring-IoC容器和Bean简介"><a href="#1-Spring-IoC容器和Bean简介" class="headerlink" title="1 Spring IoC容器和Bean简介"></a>1 Spring IoC容器和Bean简介</h1><h2 id="1-1-了解IOC"><a href="#1-1-了解IOC" class="headerlink" title="1.1 了解IOC"></a>1.1 了解IOC</h2><h3 id="1-1-1-Bean"><a href="#1-1-1-Bean" class="headerlink" title="1.1.1 Bean"></a>1.1.1 Bean</h3><p>什么是<strong>Bean</strong>?</p>
<blockquote>
<p>在Spring中，构成应用程序主干并由Spring IoC容器管理的对象称为bean。Bean是由Spring<br>IoC容器<strong>实例化</strong>，<strong>组装</strong>和<strong>管理</strong>的对象。</p>
</blockquote>
<p>显然这里的Bean并不只是那些<strong>实体类</strong>，即<strong>POJO</strong>。这里的Bean包含了所有的由Spring托管的Java类的实例！</p>
<blockquote>
<p>Bean及其之间的<strong>依赖关系</strong>反映在容器使用的<strong>配置元数据</strong>（Configuration Metadata）中。</p>
</blockquote>
<p>这里的配置元数据往往用<code>.xml</code>文件或者Java<strong>注解</strong> (<code>annotation</code>)实现。我们马上就能看到具体的例子。</p>
<h3 id="1-1-2-IOC容器"><a href="#1-1-2-IOC容器" class="headerlink" title="1.1.2 IOC容器"></a>1.1.2 IOC容器</h3><p>帮助我们管理Java对象的容器就称为Spring IOC 容器。</p>
<blockquote>
<p>在<code>org.springframework.beans</code>和<code>org.springframework.context</code>包是Spring框架的IoC容器的基础</p>
</blockquote>
<ul>
<li>它们的maven依赖为<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">&lt;!-- https://mvnrepository.com/artifact/org.springframework/spring-core --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.springframework<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>spring-core<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">version</span>&gt;</span>5.2.9.RELEASE<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br><span class="line"></span><br><span class="line"><span class="comment">&lt;!-- https://mvnrepository.com/artifact/org.springframework/spring-context --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.springframework<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>spring-context<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">version</span>&gt;</span>5.2.9.RELEASE<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br></pre></td></tr></table></figure></li>
</ul>
<h2 id="1-2-容器概述"><a href="#1-2-容器概述" class="headerlink" title="1.2 容器概述"></a>1.2 容器概述</h2><blockquote>
<p><code>org.springframework.context.ApplicationContext</code>接口代表Spring IoC容器，并负责实例化，配置和组装Bean。<br>容器通过读取配置元数据获取有关要实例化，配置和组装哪些对象的指令。配置元数据以XML，Java批注或Java代码表示。</p>
</blockquote>
<p>注意<code>ApplicationContext</code>是一个<strong>接口</strong>，通常创建<code>ClassPathXmlApplicationContext</code> 或的实例 <code>FileSystemXmlApplicationContext</code>（顾名思义，一个通过类路径，一个通过系统文件名）。</p>
<h3 id="1-2-1-配置元数据"><a href="#1-2-1-配置元数据" class="headerlink" title="1.2.1 配置元数据"></a>1.2.1 配置元数据</h3><blockquote>
<p>Spring IoC容器使用一种形式的配置元数据。此配置元数据表示您作为应用程序开发人员如何告诉Spring容器在应用程序中实例化，配置和组装对象。</p>
</blockquote>
<p>这里<strong>元数据Meta data</strong>实际上就是表明对象如何创建，如何组装，如何管理。（否则Spring怎么按照我们的意愿创建出我们想要的对象？）。</p>
<ul>
<li>配置的形式<ul>
<li><p><strong>XML</strong></p>
<p>  这也是最传统的方式，也就是所谓的XML配Bean的方式</p>
</li>
<li><p><strong>注解</strong>（annotation）<br>  基于注释的配置：Spring 2.5引入了对基于注释的配置元数据的支持。</p>
</li>
<li><p><strong>基于Java的配置</strong><br>  (这个从Spring3.0开始支持)</p>
</li>
</ul>
</li>
</ul>
<p>基于注解和Java的配置算是Spring后期发展的产物，这里我们就以最传统的XML为例。</p>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">&lt;?xml version=<span class="string">&quot;1.0&quot;</span> encoding=<span class="string">&quot;UTF-8&quot;</span>?&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">beans</span> <span class="attr">xmlns</span>=<span class="string">&quot;http://www.springframework.org/schema/beans&quot;</span></span></span><br><span class="line"><span class="tag">    <span class="attr">xmlns:xsi</span>=<span class="string">&quot;http://www.w3.org/2001/XMLSchema-instance&quot;</span></span></span><br><span class="line"><span class="tag">    <span class="attr">xsi:schemaLocation</span>=<span class="string">&quot;http://www.springframework.org/schema/beans</span></span></span><br><span class="line"><span class="string"><span class="tag">        https://www.springframework.org/schema/beans/spring-beans.xsd&quot;</span>&gt;</span></span><br><span class="line"></span><br><span class="line">    <span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;...&quot;</span> <span class="attr">class</span>=<span class="string">&quot;...&quot;</span>&gt;</span>  </span><br><span class="line">        <span class="comment">&lt;!-- collaborators and configuration for this bean go here --&gt;</span></span><br><span class="line">    <span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br><span class="line"></span><br><span class="line">    <span class="comment">&lt;!-- more bean definitions go here --&gt;</span></span><br><span class="line"></span><br><span class="line"><span class="tag">&lt;/<span class="name">beans</span>&gt;</span></span><br></pre></td></tr></table></figure>

<p>其中<code>id</code>是定义单个Bean的唯一唯一表示，<code>class</code>要使用<strong>全限定名</strong>（除非用到后面的<strong>别名</strong>）。</p>
<h3 id="1-2-2-实例化容器"><a href="#1-2-2-实例化容器" class="headerlink" title="1.2.2 实例化容器"></a>1.2.2 实例化容器</h3><p>为了学习笔记的精简化，完整的代码不在这里提供，具体代码可参见 <a target="_blank" rel="noopener" href="https://song-yang-ji.blog.csdn.net/article/details/109662902">这篇博客</a>。</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="type">ApplicationContext</span> <span class="variable">context</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">ClassPathXmlApplicationContext</span>(<span class="string">&quot;beans.xml&quot;</span>);</span><br></pre></td></tr></table></figure>

<h3 id="1-2-3-使用容器"><a href="#1-2-3-使用容器" class="headerlink" title="1.2.3  使用容器"></a>1.2.3  使用容器</h3><p>我们可以使用<code>ApplicationContext</code>来访问有IOC容器托管的对象。</p>
<ul>
<li><p>方式1</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">T <span class="title function_">getBean</span><span class="params">(String name)</span></span><br><span class="line"><span class="type">User</span> <span class="variable">user</span> <span class="operator">=</span> (User)applicationContext.getBean(<span class="string">&quot;user&quot;</span>);</span><br></pre></td></tr></table></figure>
</li>
<li><p>方式2</p>
</li>
</ul>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">T <span class="title function_">getBean</span><span class="params">(String name, Class&lt;T&gt; requiredType)</span></span><br><span class="line"><span class="type">User</span> <span class="variable">user</span> <span class="operator">=</span> applicationContext.getBean(<span class="string">&quot;user&quot;</span>,User.class);</span><br></pre></td></tr></table></figure>

<p>总结，方式一使用<strong>类型强制转换</strong>，方式二使用类型做参数，错误可以在编译时期发现，更好。</p>
<h2 id="1-3-Bean"><a href="#1-3-Bean" class="headerlink" title="1.3 Bean"></a>1.3 Bean</h2><h3 id="1-3-1-Bean-的命名"><a href="#1-3-1-Bean-的命名" class="headerlink" title="1.3.1 Bean 的命名"></a>1.3.1 Bean 的命名</h3><ul>
<li><p><strong>命名约定</strong><br>使用<strong>驼峰式命名</strong>，如<code>accountManager， accountService，userDao，loginController</code>。</p>
</li>
<li><p>Bean 的标识</p>
</li>
</ul>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;user&quot;</span> <span class="attr">name</span>=<span class="string">&quot;user2,user3,user4&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.jsy.pojo.User&quot;</span>&gt;</span></span><br><span class="line">        <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;name&quot;</span> <span class="attr">value</span>=<span class="string">&quot;JSY&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>
<p>使用<code>id</code>来唯一标识bean，<code>name</code>是别名,可以有多个。<code>@Bean</code><br>注解也可以提供别名。</p>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;user&quot;</span> <span class="attr">name</span>=<span class="string">&quot;user2,user3,user4&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.jsy.pojo.User&quot;</span>&gt;</span></span><br><span class="line"> <span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>

<ul>
<li><strong>不提供名称</strong><br>为什么允许这样做，可以猜想就类似于匿名内部类一样，无需提供名称。<br>这和后面的<strong>自动装配</strong>有关。</li>
</ul>
<h3 id="1-3-2-Bean-的实例化"><a href="#1-3-2-Bean-的实例化" class="headerlink" title="1.3.2 Bean 的实例化"></a>1.3.2 Bean 的实例化</h3><p><del>这部分和类的初始化相关，暂且不谈</del> </p>
<h2 id="1-4-依赖（Dependencies）"><a href="#1-4-依赖（Dependencies）" class="headerlink" title="1.4 依赖（Dependencies）"></a>1.4 依赖（Dependencies）</h2><blockquote>
<p>典型的企业应用程序不包含单个对象（或Spring术语中的bean）。即使是最简单的应用程序，也有一些对象可以协同工作，以呈现最终用户视为一致的应用程序。</p>
</blockquote>
<p>简单的说，就是对象的构成很多时候是依赖其他多个对象的。比如， <code>Zoo</code>实例依赖<code>Tiger</code>，<code>Lion</code>实例;<code>UserService</code>实例依赖<code>UserDao</code>或者<code>UserMapper</code>实例。</p>
<blockquote>
<p>使用DI原理，代码更加简洁，当为对象提供依赖项时，去耦会更有效。该对象不查找其依赖项，并且不知道依赖项的位置或类。</p>
</blockquote>
<p>也就是，程序员不在负责对象的创建和组装，而仅仅负责对象的提供，创建及组装（DI)由Spring 完成。</p>
<p>综上， <strong>DI</strong>实际上是实现<strong>IOC</strong>的一种措施。</p>
<h3 id="1-4-1-依赖注入"><a href="#1-4-1-依赖注入" class="headerlink" title="1.4.1 依赖注入"></a>1.4.1 依赖注入</h3><h4 id="1-4-1-1-Constructor-注入"><a href="#1-4-1-1-Constructor-注入" class="headerlink" title="1.4.1.1 Constructor 注入"></a>1.4.1.1 Constructor 注入</h4><p>实体类</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.jsy.pojo;</span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Zoo</span> &#123;</span><br><span class="line">    Tiger tiger;</span><br><span class="line">    Lion lion;</span><br><span class="line"></span><br><span class="line">    <span class="keyword">public</span> <span class="title function_">Zoo</span><span class="params">(Tiger tiger, Lion lion)</span> &#123;</span><br><span class="line">        <span class="built_in">this</span>.tiger = tiger;</span><br><span class="line">        <span class="built_in">this</span>.lion = lion;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br><span class="line"></span><br></pre></td></tr></table></figure>

<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;zoo&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.jsy.pojo.Zoo&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">ref</span>=<span class="string">&quot;lion&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">constructor-arg</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">ref</span>=<span class="string">&quot;tiger&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">constructor-arg</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br><span class="line"></span><br><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;lion&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.jsy.pojo.Lion&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;tiger&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.jsy.pojo.Tiger&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>

<ul>
<li>构造函数参数解析匹配通过使用<strong>参数的类型</strong>进行</li>
</ul>
<p>上述的例子中<code>Lion</code> 、<code>Tiger</code>类不是通过继承关联的，则不存在潜在的歧义，配置生效，</p>
<p>（<del>以下的例子来自官方</del>）</p>
<ul>
<li><strong>type</strong> 属性</li>
</ul>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;exampleBean&quot;</span> <span class="attr">class</span>=<span class="string">&quot;examples.ExampleBean&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">type</span>=<span class="string">&quot;int&quot;</span> <span class="attr">value</span>=<span class="string">&quot;7500000&quot;</span>/&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">type</span>=<span class="string">&quot;java.lang.String&quot;</span> <span class="attr">value</span>=<span class="string">&quot;42&quot;</span>/&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>

<ul>
<li><strong>index</strong> 属性</li>
</ul>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;exampleBean&quot;</span> <span class="attr">class</span>=<span class="string">&quot;examples.ExampleBean&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">type</span>=<span class="string">&quot;int&quot;</span> <span class="attr">value</span>=<span class="string">&quot;7500000&quot;</span>/&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">type</span>=<span class="string">&quot;java.lang.String&quot;</span> <span class="attr">value</span>=<span class="string">&quot;42&quot;</span>/&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>

<ul>
<li><strong>name</strong> 属性</li>
</ul>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;exampleBean&quot;</span> <span class="attr">class</span>=<span class="string">&quot;examples.ExampleBean&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">name</span>=<span class="string">&quot;years&quot;</span> <span class="attr">value</span>=<span class="string">&quot;7500000&quot;</span>/&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">name</span>=<span class="string">&quot;ultimateAnswer&quot;</span> <span class="attr">value</span>=<span class="string">&quot;42&quot;</span>/&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>


<h4 id="1-4-1-2-Setter-注入"><a href="#1-4-1-2-Setter-注入" class="headerlink" title="1.4.1.2 Setter 注入"></a>1.4.1.2 Setter 注入</h4><blockquote>
<p>基于设置器的DI是通过在调用无参数构造函数或无参数static工厂方法以实例化您的bean之后，在您的bean上调用setter方法来完成的。</p>
</blockquote>
<ul>
<li>必须具有无参构造器</li>
<li>必须有set函数，函数名为 set+属性名（首字母大写）</li>
</ul>
<h4 id="1-4-1-3-Factory方法注入"><a href="#1-4-1-3-Factory方法注入" class="headerlink" title="1.4.1.3 Factory方法注入"></a>1.4.1.3 Factory方法注入</h4><p>这种方法与上述两种原理是一致的，区别不大。</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">ExampleBean</span> &#123;</span><br><span class="line"></span><br><span class="line">    <span class="comment">// a private constructor</span></span><br><span class="line">    <span class="keyword">private</span> <span class="title function_">ExampleBean</span><span class="params">(...)</span> &#123;</span><br><span class="line">        ...</span><br><span class="line">    &#125;</span><br><span class="line"></span><br><span class="line">    <span class="comment">// a static factory method; the arguments to this method can be</span></span><br><span class="line">    <span class="comment">// considered the dependencies of the bean that is returned,</span></span><br><span class="line">    <span class="comment">// regardless of how those arguments are actually used.</span></span><br><span class="line">    <span class="keyword">public</span> <span class="keyword">static</span> ExampleBean <span class="title function_">createInstance</span> <span class="params">(</span></span><br><span class="line"><span class="params">        AnotherBean anotherBean, YetAnotherBean yetAnotherBean, <span class="type">int</span> i)</span> &#123;</span><br><span class="line"></span><br><span class="line">        <span class="type">ExampleBean</span> <span class="variable">eb</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">ExampleBean</span> (...);</span><br><span class="line">        <span class="comment">// some other operations...</span></span><br><span class="line">        <span class="keyword">return</span> eb;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;exampleBean&quot;</span> <span class="attr">class</span>=<span class="string">&quot;examples.ExampleBean&quot;</span> <span class="attr">factory-method</span>=<span class="string">&quot;createInstance&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">ref</span>=<span class="string">&quot;anotherExampleBean&quot;</span>/&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">ref</span>=<span class="string">&quot;yetAnotherBean&quot;</span>/&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">constructor-arg</span> <span class="attr">value</span>=<span class="string">&quot;1&quot;</span>/&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br><span class="line"></span><br><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;anotherExampleBean&quot;</span> <span class="attr">class</span>=<span class="string">&quot;examples.AnotherBean&quot;</span>/&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;yetAnotherBean&quot;</span> <span class="attr">class</span>=<span class="string">&quot;examples.YetAnotherBean&quot;</span>/&gt;</span></span><br></pre></td></tr></table></figure>

<blockquote>
<p>实例（非静态）工厂方法可以以基本上相同的方式使用（除了使用factory-bean属性代替使用class属性外）</p>
</blockquote>
<h4 id="1-4-1-4-循环依赖问题"><a href="#1-4-1-4-循环依赖问题" class="headerlink" title="1.4.1.4 循环依赖问题"></a>1.4.1.4 循环依赖问题</h4><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.jsy.pojo;</span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">A</span> &#123;</span><br><span class="line">    B b;</span><br><span class="line"></span><br><span class="line">    <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">setB</span><span class="params">(B b)</span> &#123;</span><br><span class="line">        <span class="built_in">this</span>.b = b;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="keyword">package</span> com.jsy.pojo;</span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">B</span> &#123;</span><br><span class="line">    A a;</span><br><span class="line"></span><br><span class="line">    <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">setA</span><span class="params">(A a)</span> &#123;</span><br><span class="line">        <span class="built_in">this</span>.a = a;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"></span><br></pre></td></tr></table></figure>

<blockquote>
<p>使用构造函数注入，则可能会创建无法解决的循环依赖方案<br>一种可能的解决方案是编辑某些类的源代码，这些类的源代码由设置者而不是构造函数来配置。或者，避免构造函数注入，而仅使用setter注入。换句话说，尽管不建议这样做，但是您可以使用setter注入配置循环依赖关系。</p>
</blockquote>
<p>简单的说，如果出现<strong>循环依赖</strong>，必须使用<strong>setter</strong>注入。</p>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;a&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.jsy.pojo.A&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;b&quot;</span> <span class="attr">ref</span>=<span class="string">&quot;b&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br><span class="line"></span><br><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;b&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.jsy.pojo.B&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;a&quot;</span> <span class="attr">ref</span>=<span class="string">&quot;a&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>


<h3 id="1-4-2-依赖注入的细节"><a href="#1-4-2-依赖注入的细节" class="headerlink" title="1.4.2 依赖注入的细节"></a>1.4.2 依赖注入的细节</h3><p><strong>setter</strong>注入使用<code>&lt;property/&gt;</code><br><strong>constructor</strong> 注入使用<code>&lt;constructor-arg/&gt;元素</code> </p>
<p>下面主要是<strong>setter</strong>注入解释。</p>
<h4 id="1-4-2-1-真值注入"><a href="#1-4-2-1-真值注入" class="headerlink" title="1.4.2.1 真值注入"></a>1.4.2.1 真值注入</h4><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;student&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.jsy.pojo.Student&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;age&quot;</span> <span class="attr">value</span>=<span class="string">&quot;18&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;name&quot;</span> <span class="attr">value</span>=<span class="string">&quot;Mike&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>

<h4 id="1-4-2-2-Bean注入"><a href="#1-4-2-2-Bean注入" class="headerlink" title="1.4.2.2 Bean注入"></a>1.4.2.2 Bean注入</h4><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;zoo&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.jsy.pojo.Zoo&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;lion&quot;</span> <span class="attr">ref</span>=<span class="string">&quot;lion&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br><span class="line">   	<span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;tiger&quot;</span> <span class="attr">ref</span>=<span class="string">&quot;tiger&quot;</span>&gt;</span><span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>

<h4 id="1-4-2-3-空串和NULL"><a href="#1-4-2-3-空串和NULL" class="headerlink" title="1.4.2.3 空串和NULL"></a>1.4.2.3 空串和NULL</h4><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">class</span>=<span class="string">&quot;ExampleBean&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;email&quot;</span> <span class="attr">value</span>=<span class="string">&quot;&quot;</span>/&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>

<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">class</span>=<span class="string">&quot;ExampleBean&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;email&quot;</span>&gt;</span><span class="tag">&lt;<span class="name">null</span>/&gt;</span><span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>

<blockquote>
<p>下面的例子来自Kuangshen.</p>
</blockquote>
<h4 id="1-4-2-4-数组注入"><a href="#1-4-2-4-数组注入" class="headerlink" title="1.4.2.4 数组注入"></a>1.4.2.4 数组注入</h4><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;student&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.kuang.pojo.Student&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;name&quot;</span> <span class="attr">value</span>=<span class="string">&quot;小明&quot;</span>/&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;address&quot;</span> <span class="attr">ref</span>=<span class="string">&quot;addr&quot;</span>/&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;books&quot;</span>&gt;</span></span><br><span class="line">        <span class="tag">&lt;<span class="name">array</span>&gt;</span></span><br><span class="line">            <span class="tag">&lt;<span class="name">value</span>&gt;</span>西游记<span class="tag">&lt;/<span class="name">value</span>&gt;</span></span><br><span class="line">            <span class="tag">&lt;<span class="name">value</span>&gt;</span>红楼梦<span class="tag">&lt;/<span class="name">value</span>&gt;</span></span><br><span class="line">            <span class="tag">&lt;<span class="name">value</span>&gt;</span>水浒传<span class="tag">&lt;/<span class="name">value</span>&gt;</span></span><br><span class="line">        <span class="tag">&lt;/<span class="name">array</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>

<h4 id="1-4-2-5-List注入"><a href="#1-4-2-5-List注入" class="headerlink" title="1.4.2.5 List注入"></a>1.4.2.5 List注入</h4><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;hobbys&quot;</span>&gt;</span></span><br><span class="line">     <span class="tag">&lt;<span class="name">list</span>&gt;</span></span><br><span class="line">         <span class="tag">&lt;<span class="name">value</span>&gt;</span>听歌<span class="tag">&lt;/<span class="name">value</span>&gt;</span></span><br><span class="line">         <span class="tag">&lt;<span class="name">value</span>&gt;</span>看电影<span class="tag">&lt;/<span class="name">value</span>&gt;</span></span><br><span class="line">         <span class="tag">&lt;<span class="name">value</span>&gt;</span>爬山<span class="tag">&lt;/<span class="name">value</span>&gt;</span></span><br><span class="line">     <span class="tag">&lt;/<span class="name">list</span>&gt;</span></span><br><span class="line"> <span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br></pre></td></tr></table></figure>


<h4 id="1-4-2-6-Map注入"><a href="#1-4-2-6-Map注入" class="headerlink" title="1.4.2.6 Map注入"></a>1.4.2.6 Map注入</h4><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;card&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">map</span>&gt;</span></span><br><span class="line">        <span class="tag">&lt;<span class="name">entry</span> <span class="attr">key</span>=<span class="string">&quot;中国邮政&quot;</span> <span class="attr">value</span>=<span class="string">&quot;456456456465456&quot;</span>/&gt;</span></span><br><span class="line">        <span class="tag">&lt;<span class="name">entry</span> <span class="attr">key</span>=<span class="string">&quot;建设&quot;</span> <span class="attr">value</span>=<span class="string">&quot;1456682255511&quot;</span>/&gt;</span></span><br><span class="line">    <span class="tag">&lt;/<span class="name">map</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br></pre></td></tr></table></figure>

<h4 id="1-4-2-7-Set注入"><a href="#1-4-2-7-Set注入" class="headerlink" title="1.4.2.7 Set注入"></a>1.4.2.7 Set注入</h4><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;games&quot;</span>&gt;</span></span><br><span class="line">     <span class="tag">&lt;<span class="name">set</span>&gt;</span></span><br><span class="line">         <span class="tag">&lt;<span class="name">value</span>&gt;</span>LOL<span class="tag">&lt;/<span class="name">value</span>&gt;</span></span><br><span class="line">         <span class="tag">&lt;<span class="name">value</span>&gt;</span>BOB<span class="tag">&lt;/<span class="name">value</span>&gt;</span></span><br><span class="line">         <span class="tag">&lt;<span class="name">value</span>&gt;</span>COC<span class="tag">&lt;/<span class="name">value</span>&gt;</span></span><br><span class="line">     <span class="tag">&lt;/<span class="name">set</span>&gt;</span></span><br><span class="line"> <span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br></pre></td></tr></table></figure>


<h4 id="1-4-2-8-Properties注入"><a href="#1-4-2-8-Properties注入" class="headerlink" title="1.4.2.8 Properties注入"></a>1.4.2.8 Properties注入</h4><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;info&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">props</span>&gt;</span></span><br><span class="line">        <span class="tag">&lt;<span class="name">prop</span> <span class="attr">key</span>=<span class="string">&quot;学号&quot;</span>&gt;</span>20190604<span class="tag">&lt;/<span class="name">prop</span>&gt;</span></span><br><span class="line">        <span class="tag">&lt;<span class="name">prop</span> <span class="attr">key</span>=<span class="string">&quot;性别&quot;</span>&gt;</span>男<span class="tag">&lt;/<span class="name">prop</span>&gt;</span></span><br><span class="line">        <span class="tag">&lt;<span class="name">prop</span> <span class="attr">key</span>=<span class="string">&quot;姓名&quot;</span>&gt;</span>小明<span class="tag">&lt;/<span class="name">prop</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;/<span class="name">props</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">property</span>&gt;</span></span><br></pre></td></tr></table></figure>

<h4 id="1-4-2-9-p-命名空间与c-命名空间"><a href="#1-4-2-9-p-命名空间与c-命名空间" class="headerlink" title="1.4.2.9 p-命名空间与c-命名空间"></a>1.4.2.9 p-命名空间与c-命名空间</h4><ul>
<li>p-空间<br>依赖于<code>setter</code>方法的依赖注入<br>在头文件中导入约束xml名称空间 : xmlns:p&#x3D;<a target="_blank" rel="noopener" href="http://www.springframework.org/schema/p">传送门</a><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">&lt;!--P(属性: properties)命名空间 , 属性依然要设置set方法, 无参构造器仍然要有--&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;user&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.jsy.pojo.User&quot;</span> <span class="attr">p:name</span>=<span class="string">&quot;jsy&quot;</span> <span class="attr">p:spouse-ref</span>=<span class="string">&quot;address&quot;</span>/&gt;</span></span><br></pre></td></tr></table></figure></li>
</ul>
<p>注意对于bean的注入必须在字段名后面加上<code>-ref</code>，否则bean初始化出错。</p>
<ul>
<li>c-空间<br>依赖于<strong>构造函数</strong>;<br>须导入名称空间：xmlns:c&#x3D;[传送门](<a target="_blank" rel="noopener" href="http://www.springframework.org/schema/c%EF%BC%89">http://www.springframework.org/schema/c）</a><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">&lt;!--C(构造: Constructor)命名空间&gt;</span></span><br><span class="line"><span class="comment">&lt;bean id=&quot;user&quot; class=&quot;com.jsy.pojo.User&quot; c:name=&quot;jsy&quot; c:age=&quot;18&quot;/&gt;</span></span><br></pre></td></tr></table></figure></li>
</ul>
<h4 id="1-4-2-10-复合属性名称"><a href="#1-4-2-10-复合属性名称" class="headerlink" title="1.4.2.10 复合属性名称"></a>1.4.2.10 复合属性名称</h4><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;something&quot;</span> <span class="attr">class</span>=<span class="string">&quot;things.ThingOne&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;fred.bob.sammy&quot;</span> <span class="attr">value</span>=<span class="string">&quot;123&quot;</span> /&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br></pre></td></tr></table></figure>

<p>相当于一直递归地设置属性。</p>
<h3 id="1-4-3-depends-on"><a href="#1-4-3-depends-on" class="headerlink" title="1.4.3 depends-on"></a>1.4.3 depends-on</h3><p><strong>bean</strong>的依赖关系除了使用 <code>&lt;ref&gt;</code>元素表示之外，<br>可以显示的使用<code>depends-on</code>属性：</p>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;beanOne&quot;</span> <span class="attr">class</span>=<span class="string">&quot;ExampleBean&quot;</span> <span class="attr">depends-on</span>=<span class="string">&quot;manager,accountDao&quot;</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">property</span> <span class="attr">name</span>=<span class="string">&quot;manager&quot;</span> <span class="attr">ref</span>=<span class="string">&quot;manager&quot;</span> /&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">bean</span>&gt;</span></span><br><span class="line"></span><br><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;manager&quot;</span> <span class="attr">class</span>=<span class="string">&quot;ManagerBean&quot;</span> /&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;accountDao&quot;</span> <span class="attr">class</span>=<span class="string">&quot;x.y.jdbc.JdbcAccountDao&quot;</span> /&gt;</span></span><br></pre></td></tr></table></figure>
<p>有时bean之间的依赖关系不太直接。<br>也就是说，一个bean没有直接使用另一个bean，这个时候如果好像配置这种依赖关系，就要使用depends-on了。<br>使用它，可以强制指定bean的初始化顺序以及销毁顺序。</p>
<h3 id="1-4-4-Bean的懒加载"><a href="#1-4-4-Bean的懒加载" class="headerlink" title="1.4.4 Bean的懒加载"></a>1.4.4 Bean的懒加载</h3><blockquote>
<p>默认情况下，ApplicationContext实现会在初始化过程中创建和配置所有 单例（singleton）bean。</p>
</blockquote>
<p>如果不希望使用此行为，则可以通过将bean定义标记为延迟初始化来防止单例bean的预实例化。延迟初始化的bean告诉IoC容器<strong>在首次请求时而不是在启动时</strong>创建一个bean实例。</p>
<p>使用<code>lazy-init</code>属性。</p>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">&lt;!-- 默认的 情况 --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">name</span>=<span class="string">&quot;not.lazy&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.something.AnotherBean&quot;</span>/&gt;</span></span><br><span class="line"><span class="comment">&lt;!-- 懒加载 --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">bean</span> <span class="attr">id</span>=<span class="string">&quot;lazy&quot;</span> <span class="attr">class</span>=<span class="string">&quot;com.something.ExpensiveToCreateBean&quot;</span> <span class="attr">lazy-init</span>=<span class="string">&quot;true&quot;</span>/&gt;</span></span><br><span class="line"></span><br><span class="line"><span class="comment">&lt;!-- 可以直接在 容器级别上进行所有 bean的懒初始化 --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">beans</span> <span class="attr">default-lazy-init</span>=<span class="string">&quot;true&quot;</span>&gt;</span></span><br><span class="line">    <span class="comment">&lt;!-- no beans will be pre-instantiated... --&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">beans</span>&gt;</span></span><br></pre></td></tr></table></figure>


<h3 id="1-4-5-自动装配"><a href="#1-4-5-自动装配" class="headerlink" title="1.4.5 自动装配"></a>1.4.5 自动装配</h3><p>这里并不打算讲在spring中基于xml的自动装配，后面会基于<strong>注解</strong>来实现自动装配，故这里略去不谈。</p>
<h3 id="1-4-6-方法注入"><a href="#1-4-6-方法注入" class="headerlink" title="1.4.6 方法注入"></a>1.4.6 方法注入</h3><blockquote>
<p>方法注入是Spring IoC容器的一项高级功能，这里只讲解决办法。</p>
</blockquote>
<p>这里只讲一下为什么需要方法注入。</p>
<p>简单来说，由于bean的声明周期不同，导致的问题。比如一个单例的bean依赖一个原型的bean，但是单例的bean的属性注入只有一次机会，这个时候就产生了问题。</p>
<p>使用 <code>@Lookup</code> 注解。</p>
<ol>
<li><p>声明一个原型bean。</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@Component</span></span><br><span class="line"><span class="meta">@Scope(&quot;prototype&quot;)</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">MyPrototype</span> &#123;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
</li>
<li><p>在单例bean写一个返回 null 的 getXXX方法，<br><strong>这里的方法名实际上就是xml的 bean的id</strong>。<br>再用<code>@Lookup</code>标记方法。</p>
</li>
</ol>
<p>（这里也可以直接写成抽象方法，但不管怎样到最后，<strong>Spring框架都要通过使用CGLIB库中的字节码生成来动态生成覆盖该方法的子类，从而实现此方法注入</strong>）</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@Component</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">MySingleton</span> &#123;</span><br><span class="line"></span><br><span class="line">    <span class="meta">@Lookup</span></span><br><span class="line">    <span class="keyword">public</span> MyPrototype <span class="title function_">getMyPrototype</span><span class="params">()</span> &#123;</span><br><span class="line">        <span class="keyword">return</span> <span class="literal">null</span>;</span><br><span class="line">    &#125;</span><br><span class="line">    </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<ol start="3">
<li>获取 原型bean，然后使用。</li>
</ol>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">show</span><span class="params">()</span> &#123;</span><br><span class="line">		<span class="comment">// 这里返回的可不是 null，放心使用它</span></span><br><span class="line">        <span class="type">MyPrototype</span> <span class="variable">myPrototype</span> <span class="operator">=</span> getMyPrototype();</span><br><span class="line">        System.out.println(myPrototype.hashCode());</span><br><span class="line">    &#125;</span><br></pre></td></tr></table></figure>


<blockquote>
<p>参考资料</p>
<p><a target="_blank" rel="noopener" href="https://docs.spring.io/spring-framework/docs/current-SNAPSHOT/reference/html/core.html#spring-core">Spring官方文档</a></p>
<p><a target="_blank" rel="noopener" href="https://docs.spring.io/spring-framework/docs/">doc index</a></p>
</blockquote>

    </div>

    
    
    

    <footer class="post-footer">
          <div class="post-tags">
              <a href="/tags/Spring%E6%A0%B8%E5%BF%83/" rel="tag"># Spring核心</a>
              <a href="/tags/JavaEE/" rel="tag"># JavaEE</a>
          </div>

        

          <div class="post-nav">
            <div class="post-nav-item">
                <a href="/2021/04/02/SpringMVC%20%E5%B8%B8%E7%94%A8%E6%B3%A8%E8%A7%A3/" rel="prev" title="SpringMVC 常用注解">
                  <i class="fa fa-chevron-left"></i> SpringMVC 常用注解
                </a>
            </div>
            <div class="post-nav-item">
                <a href="/2021/07/05/Spring%20%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B02%20%20%E2%80%94%E2%80%94%20%20IOC%E5%AE%B9%E5%99%A8%202%20%EF%BC%88Bean%E7%9A%84%E4%BD%9C%E7%94%A8%E5%9F%9F%E3%80%81%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F%E5%9B%9E%E8%B0%83%E6%8E%A5%E5%8F%A3%EF%BC%89/" rel="next" title="Spring 学习笔记2  ——  IOC容器 2 （Bean的作用域、生命周期回调接口）">
                  Spring 学习笔记2  ——  IOC容器 2 （Bean的作用域、生命周期回调接口） <i class="fa fa-chevron-right"></i>
                </a>
            </div>
          </div>
    </footer>
  </article>
</div>






</div>
  </main>

  <footer class="footer">
    <div class="footer-inner">


<div class="copyright">
  &copy; 
  <span itemprop="copyrightYear">2023</span>
  <span class="with-love">
    <i class="fa fa-heart"></i>
  </span>
  <span class="author" itemprop="copyrightHolder">SongyangJi</span>
</div>
  <div class="powered-by">由 <a href="https://hexo.io/" rel="noopener" target="_blank">Hexo</a> & <a href="https://theme-next.js.org/muse/" rel="noopener" target="_blank">NexT.Muse</a> 强力驱动
  </div>

    </div>
  </footer>

  
  <div class="toggle sidebar-toggle" role="button">
    <span class="toggle-line"></span>
    <span class="toggle-line"></span>
    <span class="toggle-line"></span>
  </div>
  <div class="sidebar-dimmer"></div>
  <div class="back-to-top" role="button" aria-label="返回顶部">
    <i class="fa fa-arrow-up fa-lg"></i>
    <span>0%</span>
  </div>

<noscript>
  <div class="noscript-warning">Theme NexT works best with JavaScript enabled</div>
</noscript>


  
  <script src="https://cdnjs.cloudflare.com/ajax/libs/animejs/3.2.1/anime.min.js" integrity="sha256-XL2inqUJaslATFnHdJOi9GfQ60on8Wx1C2H8DYiN1xY=" crossorigin="anonymous"></script>
<script src="/js/comments.js"></script><script src="/js/utils.js"></script><script src="/js/motion.js"></script><script src="/js/schemes/muse.js"></script><script src="/js/next-boot.js"></script>

  <script src="https://cdnjs.cloudflare.com/ajax/libs/hexo-generator-searchdb/1.4.1/search.js" integrity="sha256-1kfA5uHPf65M5cphT2dvymhkuyHPQp5A53EGZOnOLmc=" crossorigin="anonymous"></script>
<script src="/js/third-party/search/local-search.js"></script>





  





</body>
</html>
